package com.youkeyi.ddy.cloud.basic.pub.server.controller;


import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.youkeyi.ddy.cloud.basic.pub.server.entity.SysServer;
import com.youkeyi.ddy.cloud.basic.pub.server.service.SysServerService;
import com.youkeyi.ddy.cloud.common.api.basic.pub.server.PublicServerCloudService;
import com.youkeyi.ddy.cloud.common.api.basic.pub.server.dto.PublicServerListCloudDto;
import com.youkeyi.ddy.cloud.common.api.basic.pub.server.dto.PublicServerListItemCloudDto;
import com.youkeyi.ddy.cloud.common.api.basic.pub.server.dto.PublicServerTreeItemCloudDto;
import com.youkeyi.ddy.cloud.common.api.basic.pub.server.param.*;
import com.youkeyi.ddy.cloud.common.constant.YoukeyiDdyCloudBasicPublicConstant;
import com.youkeyi.ddy.cloud.common.enums.ResponseCodeEnum;
import com.youkeyi.ddy.cloud.common.response.ResponseContent;
import com.youkeyi.ddy.cloud.common.utils.SimpleUUidUtils;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.*;
import java.util.stream.Collectors;

/**
 * <p>
 * 服务表 前端控制器
 * </p>
 *
 * @author xiawang.liu
 * @since 2024-02-19
 */
@Service
public class SysServerController implements PublicServerCloudService {

    @Autowired
    private SysServerService sysServerService;

    @Override
    public PublicServerListCloudDto query(PublicServerQueryCloudParam param) {
        PublicServerListCloudDto dto = new PublicServerListCloudDto();
        if (null == param) {
            dto.setErrorMessage(ResponseCodeEnum.PARAMETER_ILLEGAL.getMessage());
            return dto;
        }

        if (CollectionUtils.isNotEmpty(param.getServerPrimaryKeys())) {
            param.getServerPrimaryKeys().removeAll(Collections.singleton(null));
        }
        if (CollectionUtils.isNotEmpty(param.getCorpKeys())) {
            param.getCorpKeys().removeAll(Collections.singleton(null));
        }
        if (CollectionUtils.isNotEmpty(param.getCodes())) {
            param.getCodes().removeAll(Collections.singleton(null));
        }
        if (CollectionUtils.isNotEmpty(param.getNames())) {
            param.getNames().removeAll(Collections.singleton(null));
        }
        if (CollectionUtils.isNotEmpty(param.getParentKeys())) {
            param.getParentKeys().removeAll(Collections.singleton(null));
        }

        QueryWrapper<SysServer> wrapper = new QueryWrapper<>();
        wrapper.lambda()
                .in(CollectionUtils.isNotEmpty(param.getServerPrimaryKeys()), SysServer::getPrimaryKey, param.getServerPrimaryKeys())
                .in(CollectionUtils.isNotEmpty(param.getCorpKeys()), SysServer::getCorpKey, param.getCorpKeys())
                .in(CollectionUtils.isNotEmpty(param.getNames()), SysServer::getName, param.getNames())
                .like(StringUtils.isNotBlank(param.getNameFuzzy()), SysServer::getName, param.getNameFuzzy())
                .in(CollectionUtils.isNotEmpty(param.getCodes()), SysServer::getCode, param.getCodes())
                .like(StringUtils.isNotBlank(param.getCodeFuzzy()), SysServer::getCode, param.getCodeFuzzy())
                .in(CollectionUtils.isNotEmpty(param.getParentKeys()), SysServer::getParentKey, param.getParentKeys())
                .eq(null != param.getLevel(), SysServer::getLevel, param.getLevel())
                .ne(SysServer::getIsDeleted, YoukeyiDdyCloudBasicPublicConstant.SYSTEM_YES_OR_NO_YES.value())
        ;

        Page<SysServer> page = new Page<>();
        if (null != param.getCurrentPage() && null != param.getPageSize()) {
            page.setCurrent(param.getCurrentPage());
            page.setSize(param.getPageSize());
        } else {
            page.setCurrent(1);
            page.setSize(99999999);
        }
        Page<SysServer> serverList = sysServerService.page(page, wrapper);
        if (CollectionUtils.isNotEmpty(serverList.getRecords())) {
            dto.setTotal(serverList.getTotal());

            Map<String, String> parentKeyMap = new HashMap<>();
            if (param.getNeedParent()) {
                List<String> parentKeys = serverList.getRecords().stream().map(SysServer::getParentKey).collect(Collectors.toList());
                QueryWrapper<SysServer>queryParentWrapper = new QueryWrapper<>();
                queryParentWrapper.lambda()
                        .in(SysServer::getPrimaryKey, parentKeys)
                ;
                List<SysServer> servers = sysServerService.list(queryParentWrapper);
                if (CollectionUtils.isNotEmpty(servers)) {
                    parentKeyMap.putAll(servers.stream().collect(Collectors.toMap(SysServer::getPrimaryKey, SysServer::getName)));
                }
            }

            List<PublicServerListItemCloudDto> items = new ArrayList<>();
            serverList.getRecords().forEach(server -> {
                PublicServerListItemCloudDto item = new PublicServerListItemCloudDto();
                item.setServerPrimaryKey(server.getPrimaryKey());
                item.setCorpKey(server.getCorpKey());
                item.setName(server.getName());
                item.setCode(server.getCode());
                item.setPrice(server.getPrice());
                item.setLevel(server.getLevel());
                item.setParentKey(server.getParentKey());
                item.setParentName(parentKeyMap.get(server.getParentKey()));
                item.setPath(server.getPath());
                item.setDesc(server.getDesc());
                item.setRemark(server.getRemark());
                item.setIsDeleted(server.getIsDeleted());
                item.setIsDeletedName(YoukeyiDdyCloudBasicPublicConstant.SYSTEM_YES_OR_NO.getName(item.getIsDeleted()));
                item.setCreateTime(server.getCreateTime() != null ? server.getCreateTime().getTime() : null);
                item.setCreateUserKey(server.getCreateUserKey());
                item.setCreateUserName(server.getCreateUserName());
                item.setUpdateTime(server.getUpdateTime() != null ? server.getUpdateTime().getTime() : null);
                item.setUpdateUserKey(server.getUpdateUserKey());
                item.setUpdateUserName(server.getUpdateUserName());
                items.add(item);
            });
            dto.setRows(items);
        }
        dto.setSuccessMessage(ResponseCodeEnum.SUCCESS.getMessage());
        return dto;
    }

    @Override
    public List<PublicServerTreeItemCloudDto> queryTree(PublicServerQueryTreeCloudParam param) {
        QueryWrapper<SysServer> wrapper = new QueryWrapper<>();
        wrapper.lambda()
                .like(StringUtils.isNotBlank(param.getServerPrimaryKey()), SysServer::getPath, param.getServerPrimaryKey())
                .ne(SysServer::getIsDeleted, YoukeyiDdyCloudBasicPublicConstant.SYSTEM_YES_OR_NO_YES.value())
        ;
        List<SysServer> servers = sysServerService.list(wrapper);

        List<PublicServerTreeItemCloudDto> tree = new ArrayList<>();
        servers.forEach(server -> {
            PublicServerTreeItemCloudDto item = new PublicServerTreeItemCloudDto();
            item.setServerPrimaryKey(server.getPrimaryKey());
            item.setCorpKey(server.getCorpKey());
            item.setServerCode(server.getCode());
            item.setName(server.getName());
            item.setLevel(server.getLevel());
            item.setParentKey(server.getParentKey());
            item.setPath(server.getPath());
            item.setDesc(server.getDesc());
            item.setRemark(server.getRemark());
            tree.add(item);
        });

        // 转树
        Map<String, List<PublicServerTreeItemCloudDto>> serverByParentKeyMaps = tree.stream().collect(Collectors.groupingBy(PublicServerTreeItemCloudDto::getParentKey));
        tree.forEach(item -> item.setServerItems(serverByParentKeyMaps.get(item.getServerPrimaryKey())));
        if (StringUtils.isBlank(param.getServerPrimaryKey())) {
            return tree.stream().filter(v -> v.getServerPrimaryKey().equals(param.getServerPrimaryKey())).collect(Collectors.toList());
        }
        return tree;
    }

    @Override
    public ResponseContent create(PublicServerCreateCloudParam param) {
        ResponseContent rc = new ResponseContent();
        if (null == param
                || StringUtils.isBlank(param.getName()) || StringUtils.isBlank(param.getCode())) {
            rc.setErrorMessage(ResponseCodeEnum.PARAMETER_ILLEGAL.getMessage());
            return rc;
        }
        SysServer server = new SysServer();
        server.setPrimaryKey(SimpleUUidUtils.getUuid());
        server.setCorpKey(param.getCorpKey());
        server.setName(param.getName());
        server.setCode(StringUtils.isNotBlank(param.getCode()) ? param.getCode() : String.format("SERVER-%s", System.currentTimeMillis()));
        server.setPrice(param.getPrice());
        server.setDesc(param.getDesc());
        server.setRemark(param.getRemark());
        server.setIsDeleted(YoukeyiDdyCloudBasicPublicConstant.SYSTEM_YES_OR_NO_NO.value());
        server.setCreateUserKey(param.getCreateUserKey());
        server.setCreateUserName(param.getCreateUserName());
        server.setCreateTime(new Date());

        // 构造父级数据
        server.setLevel(0);
        server.setParentKey("");
        server.setPath(String.format("|%s|", server.getPrimaryKey()));
        if (StringUtils.isNotBlank(param.getParentKey())) {
            QueryWrapper<SysServer> queryWrapper = new QueryWrapper<>();
            queryWrapper.lambda().eq(SysServer::getPrimaryKey, param.getParentKey());
            SysServer parentServer = sysServerService.getOne(queryWrapper);
            if (null != parentServer && StringUtils.isNotBlank(parentServer.getPrimaryKey())) {
                server.setLevel(parentServer.getLevel() + 1);
                server.setParentKey(parentServer.getPrimaryKey());
                server.setPath(String.format("%s|", parentServer.getPath()));
            }
        }
        
        boolean save = sysServerService.save(server);
        if (!save) {
            rc.setErrorMessage(ResponseCodeEnum.FAIL.getMessage());
            return rc;
        }
        rc.setSuccessMessage(ResponseCodeEnum.SUCCESS.getMessage());
        rc.setKey(server.getPrimaryKey());
        return rc;
    }

    @Override
    public ResponseContent update(PublicServerUpdateCloudParam param) {
        ResponseContent rc = new ResponseContent();
        if (null == param || StringUtils.isBlank(param.getServerPrimaryKey())) {
            rc.setErrorMessage(ResponseCodeEnum.PARAMETER_ILLEGAL.getMessage());
            return rc;
        }


        QueryWrapper<SysServer> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda().eq(SysServer::getPrimaryKey, param.getServerPrimaryKey());
        SysServer myselfServer = sysServerService.getOne(queryWrapper);
        if (null == myselfServer || StringUtils.isBlank(myselfServer.getPrimaryKey())) {
            rc.setErrorMessage(ResponseCodeEnum.UNKNOWN_ERROR.getMessage());
            return rc;
        }
        
        
        UpdateWrapper<SysServer> wrapper = new UpdateWrapper<>();
        wrapper.lambda()
                .eq(SysServer::getPrimaryKey, param.getServerPrimaryKey());
        SysServer server = new SysServer();
        server.setPrimaryKey(param.getServerPrimaryKey());
        server.setName(param.getName());
        server.setCode(param.getCode());
        server.setPrice(param.getPrice());
        server.setDesc(param.getDesc());
        server.setRemark(param.getRemark());
        server.setUpdateUserKey(param.getUpdateUserKey());
        server.setUpdateUserName(param.getUpdateUserName());
        server.setUpdateTime(new Date());
        
        if (!myselfServer.getParentKey().equals(param.getParentKey())) {
            // 构造父级数据
            server.setLevel(0);
            server.setParentKey("");
            server.setPath(String.format("|%s|", server.getPrimaryKey()));
            if (StringUtils.isNotBlank(param.getParentKey())) {
                QueryWrapper<SysServer> queryParentWrapper = new QueryWrapper<>();
                queryParentWrapper.lambda().eq(SysServer::getPrimaryKey, param.getParentKey());
                SysServer parentServer = sysServerService.getOne(queryParentWrapper);
                if (null != parentServer && StringUtils.isNotBlank(parentServer.getPrimaryKey())) {
                    server.setLevel(parentServer.getLevel() + 1);
                    server.setParentKey(parentServer.getPrimaryKey());
                    server.setPath(String.format("%s|", parentServer.getPath()));
                }
            }
        }
        
        boolean save = sysServerService.update(server, wrapper);
        rc.setSuccessMessage(ResponseCodeEnum.SUCCESS.getMessage());
        if (!save) {
            rc.setErrorMessage(ResponseCodeEnum.FAIL.getMessage());
            return rc;
        }
        return rc;
    }

    @Override
    public ResponseContent delete(PublicServerDeleteCloudParam param) {
        ResponseContent rc = new ResponseContent();
        if (null == param || CollectionUtils.isEmpty(param.getServerPrimaryKeys())) {
            rc.setErrorMessage(ResponseCodeEnum.PARAMETER_ILLEGAL.getMessage());
            return rc;
        }
        UpdateWrapper<SysServer> wrapper = new UpdateWrapper<>();
        wrapper.lambda()
                .in(SysServer::getPrimaryKey, param.getServerPrimaryKeys());

        SysServer server = new SysServer();
        server.setIsDeleted(YoukeyiDdyCloudBasicPublicConstant.SYSTEM_YES_OR_NO_YES.value());
        server.setUpdateUserKey(param.getUpdateUserKey());
        server.setUpdateUserName(param.getUpdateUserName());
        server.setUpdateTime(new Date());
        boolean save = sysServerService.update(server, wrapper);
        rc.setSuccessMessage(ResponseCodeEnum.SUCCESS.getMessage());
        if (!save) {
            rc.setErrorMessage(ResponseCodeEnum.FAIL.getMessage());
        }
        return rc;
    }
}
